# -*- coding: UTF-8 -*-
import api
import config
import json
import logging
from datetime import datetime

LOG_FORMAT = "%(asctime)s - %(levelname)s - %(message)s"
logging.basicConfig(format=LOG_FORMAT, level=logging.INFO)

import os

logging.info(os.getcwd())


# todo 本教程介绍如何使用飞书开放能力，实现将外部销售额数据同步到电子表格，并对销售额进行总额统计。
#  参考官网说明：https://open.feishu.cn/document/home/sales-statistics-base-on-spreadsheets/sales-statistics-based-on-sheets
#  结合最终展示样式和需求会更快理解。


def load_sales_data():
    '''load data'''
    with open('data.json', 'r') as f:
        data = json.loads(f.read())
        return data


def column_id(col):
    '''column int to string id
    将列的值映射到Excel的列号，也就是说使用 chr() 函数将一个整数转换为对应的 ASCII 字符(A-Z)具体的某一行，以便Excel能识别到正确的行列

    减 1 的操作是为了将列号正确地映射到 Excel 列标识符。具体来说：

    m = (i-1) % 26 是为了将 i 映射到 0-25 的范围，这样我们可以使用 chr(m+65) 来获得正确的字符。例如，i=1 时，m=0，对应 'A'。

    i = (i-1) // 26 是为了正确地处理多位字符的情况。例如，i=27 时，i-1 为 26，26 // 26 结果为 1，这样下一次循环可以处理 'A'。

    这里的 'A' 对应的 ASCII 码是 65 ，以此类推 'Z' 的 ASCII 码是 90

    '''
    ans = ""
    i = col
    while i > 0:
        m = int((i - 1) % 26)
        i = int((i - 1) / 26)
        ans = chr(m + 65) + ans
    return ans


def build_values_body(sales, sheetid):
    '''build write body'''
    data = sales["data"]
    rows = len(data)
    cols = len(data[0])
    range1 = sheetid + "!A1:" + column_id(cols) + str(rows)
    # 这里根据个人的业务修改，本例中是中间隔了一列所以+2，要根据需求看
    range2 = sheetid + "!" + column_id(cols + 2) + "1:" + column_id(cols + 2) + "2"
    # 这个就是Excel的函数，没啥说的就是要找准对应的行和列拼接就行
    formula = "=SUM(" + column_id(cols) + "2:" + column_id(cols) + str(rows) + ")"
    # 构建请求体，填充对应的值，这里第二个Range是执行函数后结果写入
    # 具体函数写法参考：https://open.feishu.cn/document/server-docs/docs/sheets-v3/data-types-supported-by-sheets
    body = {
        "valueRanges": [
            {
                "range": range1,
                "values": []
            },
            {
                "range": range2,
                "values": [
                    [config.TOTAL], [{"type": "formula", "text": formula}]
                ]
            }
        ]
    }
    for d in data:
        row = []
        for c in d:
            row.append(c)
        body["valueRanges"][0]["values"].append(row)
    return body


def build_styles_body(sales, sheetid):
    '''build write body'''
    data = sales["data"]
    rows = len(data)
    cols = len(data[0])
    first_row1 = sheetid + "!A1:" + column_id(cols) + "1"
    first_row2 = sheetid + "!" + column_id(cols + 2) + "1:" + column_id(cols + 2) + "1"
    all_rows = sheetid + "!A1:" + column_id(cols + 2) + str(rows)
    # 这里就是对选中范围单元格的一些样式调整，可以参考下面进行调整：
    # 批量设置单元格样式：https://open.feishu.cn/document/server-docs/docs/sheets-v3/data-operation/batch-set-cell-style
    # 支持写入数据类型 ：https://open.feishu.cn/document/server-docs/docs/sheets-v3/data-types-supported-by-sheets
    body = {
        "data": [
            {
                "ranges": [
                    first_row1,
                    first_row2
                ],
                "style": {
                    "font": {
                        "bold": True
                    },
                    "backColor": "#21d11f",
                }
            },
            {
                "ranges": [
                    all_rows
                ],
                "style": {
                    "hAlign": 1,
                    "vAlign": 1,
                }
            }
        ]
    }
    return body


def sales_statistics():
    '''Sales statistics'''
    # init api client
    client = api.Client(config.LARK_HOST)

    # get tenant access token        
    access_token = client.get_tenant_access_token(config.APP_ID, config.APP_SECRET)

    # get app folder token
    folder_token = client.get_root_folder_token(access_token)

    # copy from template doc
    doctype = 'sheet'
    title = config.TITLE + datetime.now().strftime("%Y-%m-%d")
    token, url = client.create_spreadsheet(access_token, folder_token, title)

    # get firest sheet_id
    sheetid = client.get_first_sheetid(access_token, token)

    # load sales data
    sales = load_sales_data()

    # build values body
    body = build_values_body(sales, sheetid)

    # write to spreadsheet
    client.batch_update_values(access_token, token, body)

    # build styles body
    body = build_styles_body(sales, sheetid)

    # write to spreadsheet
    client.batch_update_styles(access_token, token, body)

    # add permissions for chat members
    client.add_permissions_member(access_token, token, doctype, "email", config.EMAIL, "edit")

    logging.info("spreadsheet URL: " + url)


if __name__ == "__main__":
    sales_statistics()
